<!DOCTYPE html>
<html lang="zh_CN">
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1">
    <meta name="generator" content="VuePress 2.0.0-beta.45">
    <style>
      :root {
        --c-bg: #fff;
      }
      html.dark {
        --c-bg: #22272e;
      }
      html, body {
        background-color: var(--c-bg);
      }
    </style>
    <script>
      const userMode = localStorage.getItem('vuepress-color-scheme');
			const systemDarkMode = window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches;
			if (userMode === 'dark' || (userMode !== 'light' && systemDarkMode)) {
				document.documentElement.classList.toggle('dark', true);
			}
    </script>
    <link rel="shortcut icon" type="image/x-icon" href="/favicon.ico"><title>模型和机制 | 科科人神</title><meta name="description" content="科科人神，后端软件工程师，喜欢云原生">
    <link rel="modulepreload" href="/assets/app.80e5dc69.js"><link rel="modulepreload" href="/assets/ensure_mechanics.html.7818d8b5.js"><link rel="modulepreload" href="/assets/ensure_mechanics.html.603c62de.js"><link rel="prefetch" href="/assets/index.html.cba988ab.js"><link rel="prefetch" href="/assets/1.html.8ac90e92.js"><link rel="prefetch" href="/assets/19.html.4444be95.js"><link rel="prefetch" href="/assets/必备知识.html.7da85c42.js"><link rel="prefetch" href="/assets/必备知识罗列.html.5e18db77.js"><link rel="prefetch" href="/assets/1.html.356f0755.js"><link rel="prefetch" href="/assets/2.html.085440fc.js"><link rel="prefetch" href="/assets/3.html.09effb5c.js"><link rel="prefetch" href="/assets/1.html.50fb5135.js"><link rel="prefetch" href="/assets/1.html.17222973.js"><link rel="prefetch" href="/assets/1.html.0a197ef1.js"><link rel="prefetch" href="/assets/4-1.html.073fbd99.js"><link rel="prefetch" href="/assets/4-2.html.64039343.js"><link rel="prefetch" href="/assets/4.html.021c0881.js"><link rel="prefetch" href="/assets/5-6-1.html.34978ed1.js"><link rel="prefetch" href="/assets/5-6-2.html.f004f560.js"><link rel="prefetch" href="/assets/5-6.html.f5ad3835.js"><link rel="prefetch" href="/assets/index.html.467e6eba.js"><link rel="prefetch" href="/assets/index.html.f3622043.js"><link rel="prefetch" href="/assets/index.html.a2792a89.js"><link rel="prefetch" href="/assets/index.html.5d63961d.js"><link rel="prefetch" href="/assets/index.html.0b5fc023.js"><link rel="prefetch" href="/assets/index.html.2f735cf1.js"><link rel="prefetch" href="/assets/index.html.9d71a6d6.js"><link rel="prefetch" href="/assets/bash_completions.html.ed68147e.js"><link rel="prefetch" href="/assets/man_docs.html.2f0dd0c9.js"><link rel="prefetch" href="/assets/md_docs.html.20de452a.js"><link rel="prefetch" href="/assets/rest_docs.html.b77e8a2e.js"><link rel="prefetch" href="/assets/zsh_completions.html.60976ab2.js"><link rel="prefetch" href="/assets/syslog.html.48554683.js"><link rel="prefetch" href="/assets/daily_dep.html.2f155f5c.js"><link rel="prefetch" href="/assets/getting_started.html.769a2eaa.js"><link rel="prefetch" href="/assets/installation.html.e6b0002b.js"><link rel="prefetch" href="/assets/migrating.html.128871c1.js"><link rel="prefetch" href="/assets/new_project.html.8326d390.js"><link rel="prefetch" href="/assets/uninstalling.html.26650652.js"><link rel="prefetch" href="/assets/deduction.html.d4acd3fa.js"><link rel="prefetch" href="/assets/404.html.a15b4cbd.js"><link rel="prefetch" href="/assets/index.html.29aac47c.js"><link rel="prefetch" href="/assets/index.html.b64fbb23.js"><link rel="prefetch" href="/assets/index.html.cd48e230.js"><link rel="prefetch" href="/assets/index.html.6b048e76.js"><link rel="prefetch" href="/assets/index.html.7f0a6e54.js"><link rel="prefetch" href="/assets/index.html.b5a71586.js"><link rel="prefetch" href="/assets/index.html.60805430.js"><link rel="prefetch" href="/assets/index.html.60736b0b.js"><link rel="prefetch" href="/assets/index.html.80dddd6d.js"><link rel="prefetch" href="/assets/index.html.cc3c6a0d.js"><link rel="prefetch" href="/assets/index.html.44e62fda.js"><link rel="prefetch" href="/assets/index.html.015a0b2c.js"><link rel="prefetch" href="/assets/index.html.415d4517.js"><link rel="prefetch" href="/assets/index.html.d1d65e23.js"><link rel="prefetch" href="/assets/index.html.725ac526.js"><link rel="prefetch" href="/assets/index.html.c824ee30.js"><link rel="prefetch" href="/assets/1.html.4fb25663.js"><link rel="prefetch" href="/assets/19.html.ded8a9c9.js"><link rel="prefetch" href="/assets/必备知识.html.0ff3a77d.js"><link rel="prefetch" href="/assets/必备知识罗列.html.85e0f635.js"><link rel="prefetch" href="/assets/1.html.4f76037b.js"><link rel="prefetch" href="/assets/2.html.05a6e91e.js"><link rel="prefetch" href="/assets/3.html.30d4c4b6.js"><link rel="prefetch" href="/assets/1.html.ce86a757.js"><link rel="prefetch" href="/assets/1.html.0f8a9434.js"><link rel="prefetch" href="/assets/1.html.f4ee2fe7.js"><link rel="prefetch" href="/assets/4-1.html.c7cc75b6.js"><link rel="prefetch" href="/assets/4-2.html.36807608.js"><link rel="prefetch" href="/assets/4.html.c03ae622.js"><link rel="prefetch" href="/assets/5-6-1.html.651e5517.js"><link rel="prefetch" href="/assets/5-6-2.html.5ccfdb5e.js"><link rel="prefetch" href="/assets/5-6.html.882bc951.js"><link rel="prefetch" href="/assets/index.html.9d9ba895.js"><link rel="prefetch" href="/assets/index.html.3da373d1.js"><link rel="prefetch" href="/assets/index.html.6ec0b380.js"><link rel="prefetch" href="/assets/index.html.f8c39be7.js"><link rel="prefetch" href="/assets/index.html.e8d4dc57.js"><link rel="prefetch" href="/assets/index.html.2275c56f.js"><link rel="prefetch" href="/assets/index.html.711c721b.js"><link rel="prefetch" href="/assets/bash_completions.html.31fa6426.js"><link rel="prefetch" href="/assets/man_docs.html.cc0f68c6.js"><link rel="prefetch" href="/assets/md_docs.html.dd10674f.js"><link rel="prefetch" href="/assets/rest_docs.html.46da86e5.js"><link rel="prefetch" href="/assets/zsh_completions.html.64d57b81.js"><link rel="prefetch" href="/assets/syslog.html.5324d692.js"><link rel="prefetch" href="/assets/daily_dep.html.b7a8b70b.js"><link rel="prefetch" href="/assets/getting_started.html.29c6534a.js"><link rel="prefetch" href="/assets/installation.html.b11da95a.js"><link rel="prefetch" href="/assets/migrating.html.92825adc.js"><link rel="prefetch" href="/assets/new_project.html.8fcfe511.js"><link rel="prefetch" href="/assets/uninstalling.html.34c1a6fb.js"><link rel="prefetch" href="/assets/deduction.html.2f0a618b.js"><link rel="prefetch" href="/assets/404.html.37719150.js"><link rel="prefetch" href="/assets/index.html.bc2fbcdd.js"><link rel="prefetch" href="/assets/index.html.2363e42b.js"><link rel="prefetch" href="/assets/index.html.691f6b43.js"><link rel="prefetch" href="/assets/index.html.c73599f4.js"><link rel="prefetch" href="/assets/index.html.32559aa6.js"><link rel="prefetch" href="/assets/index.html.283a60cc.js"><link rel="prefetch" href="/assets/index.html.b72bddc9.js"><link rel="prefetch" href="/assets/index.html.aebed871.js"><link rel="prefetch" href="/assets/index.html.1bace120.js"><link rel="prefetch" href="/assets/index.html.7913d44a.js"><link rel="prefetch" href="/assets/index.html.4e5360d4.js"><link rel="prefetch" href="/assets/index.html.028748b8.js"><link rel="prefetch" href="/assets/index.html.e9cb3a86.js"><link rel="prefetch" href="/assets/index.html.e31e8159.js"><link rel="prefetch" href="/assets/index.html.01049197.js"><link rel="prefetch" href="/assets/404.30cc8863.js"><link rel="prefetch" href="/assets/HomePage.4e823a0b.js"><link rel="prefetch" href="/assets/Layout.61f5e0fd.js"><link rel="prefetch" href="/assets/Links.8680cda6.js"><link rel="prefetch" href="/assets/Post.93b09438.js"><link rel="prefetch" href="/assets/Tags.3d9bb337.js">
    <link rel="stylesheet" href="/assets/style.8b24233a.css">
  </head>
  <body>
    <div id="app"><!--[--><div class="theme-container"><!--[--><header class="navbar is-fixed is-visible invert"><span><a href="/" class=""><span class="site-name">$ cd /home/</span></a></span><div class="navbar-items-wrapper" style=""><!--[--><!--]--><nav class="navbar-items can-hide"><!--[--><div class="navbar-item"><a href="/" class="" aria-label="home"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="0 0 20 20" fill="currentColor"><path d="M10.707 2.293a1 1 0 00-1.414 0l-7 7a1 1 0 001.414 1.414L4 10.414V17a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 011-1h2a1 1 0 011 1v2a1 1 0 001 1h2a1 1 0 001-1v-6.586l.293.293a1 1 0 001.414-1.414l-7-7z"/></svg></span><span>home</span><!--[--><!--]--></a></div><div class="navbar-item"><a href="/tags/" class="" aria-label="归档"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-1.6 -1.6 19.2 19.2" fill="currentColor"><path d="M2 2a1 1 0 011-1h4.586a1 1 0 01.707.293l7 7a1 1 0 010 1.414l-4.586 4.586a1 1 0 01-1.414 0l-7-7A1 1 0 012 6.586V2zm3.5 4a1.5 1.5 0 100-3 1.5 1.5 0 000 3z"/><path d="M1.293 7.793A1 1 0 011 7.086V2a1 1 0 00-1 1v4.586a1 1 0 00.293.707l7 7a1 1 0 001.414 0l.043-.043-7.457-7.457z"/></svg></span><span>归档</span><!--[--><!--]--></a></div><div class="navbar-item"><a href="/links/" class="" aria-label="作品合集"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-79.52 -43.52 599.04 599.04" fill="currentColor"><path d="M382.7 292.5l2.7 2.7-170-167.3c-3.5-3.5-9.7-3.7-13.8-.5L144.3 171c-4.2 3.2-4.6 8.7-1.1 12.2l68.1 64.3c3.6 3.5 9.9 3.7 14 .5l.1-.1c4.1-3.2 10.4-3 14 .5l84 81.3c3.6 3.5 3.2 9-.9 12.2l-93.2 74c-4.2 3.3-10.5 3.1-14.2-.4L63.2 268c-3.5-3.5-9.7-3.7-13.9-.5L3.5 302.4c-4.2 3.2-4.7 8.7-1.2 12.2L211 510.7s7.4 6.8 17.3-.8l198-163.9c4-3.2 4.4-8.7.7-12.2zm54.5-83.4L226.7 2.5c-1.5-1.2-8-5.5-16.3 1.1L3.6 165.7c-4.2 3.2-4.8 8.7-1.2 12.2l42.3 41.7 171.7 165.1c3.7 3.5 10.1 3.7 14.3.4l50.2-38.8-.3-.3 7.7-6c4.2-3.2 4.6-8.7.9-12.2l-57.1-54.4c-3.6-3.5-10-3.7-14.2-.5l-.1.1c-4.2 3.2-10.5 3.1-14.2-.4L109 180.8c-3.6-3.5-3.1-8.9 1.1-12.2l92.2-71.5c4.1-3.2 10.3-3 13.9.5l160.4 159c3.7 3.5 10 3.7 14.1.5l45.8-35.8c4.1-3.2 4.4-8.7.7-12.2z"/></svg></span><span>作品合集</span><!--[--><!--]--></a></div><!--]--><div class="navbar-item"><a style="cursor:pointer;"><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="0 0 24 24" fill="currentColor"><path fill="none" d="M0 0h24v24H0z"/><path d="M11 2c4.968 0 9 4.032 9 9s-4.032 9-9 9-9-4.032-9-9 4.032-9 9-9zm0 16c3.867 0 7-3.133 7-7 0-3.868-3.133-7-7-7-3.868 0-7 3.132-7 7 0 3.867 3.132 7 7 7zm8.485.071l2.829 2.828-1.415 1.415-2.828-2.829 1.414-1.414z"/></svg></span><span>搜索</span></a></div></nav><!--[--><!--]--><!----></div></header><!--]--><div class="sidebar-mask"></div><!--[--><aside class="sidebar"><nav class="navbar-items"><!--[--><div class="navbar-item"><a href="/" class="" aria-label="home"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="0 0 20 20" fill="currentColor"><path d="M10.707 2.293a1 1 0 00-1.414 0l-7 7a1 1 0 001.414 1.414L4 10.414V17a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 011-1h2a1 1 0 011 1v2a1 1 0 001 1h2a1 1 0 001-1v-6.586l.293.293a1 1 0 001.414-1.414l-7-7z"/></svg></span><span>home</span><!--[--><!--]--></a></div><div class="navbar-item"><a href="/tags/" class="" aria-label="归档"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-1.6 -1.6 19.2 19.2" fill="currentColor"><path d="M2 2a1 1 0 011-1h4.586a1 1 0 01.707.293l7 7a1 1 0 010 1.414l-4.586 4.586a1 1 0 01-1.414 0l-7-7A1 1 0 012 6.586V2zm3.5 4a1.5 1.5 0 100-3 1.5 1.5 0 000 3z"/><path d="M1.293 7.793A1 1 0 011 7.086V2a1 1 0 00-1 1v4.586a1 1 0 00.293.707l7 7a1 1 0 001.414 0l.043-.043-7.457-7.457z"/></svg></span><span>归档</span><!--[--><!--]--></a></div><div class="navbar-item"><a href="/links/" class="" aria-label="作品合集"><!--[--><!--]--><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-79.52 -43.52 599.04 599.04" fill="currentColor"><path d="M382.7 292.5l2.7 2.7-170-167.3c-3.5-3.5-9.7-3.7-13.8-.5L144.3 171c-4.2 3.2-4.6 8.7-1.1 12.2l68.1 64.3c3.6 3.5 9.9 3.7 14 .5l.1-.1c4.1-3.2 10.4-3 14 .5l84 81.3c3.6 3.5 3.2 9-.9 12.2l-93.2 74c-4.2 3.3-10.5 3.1-14.2-.4L63.2 268c-3.5-3.5-9.7-3.7-13.9-.5L3.5 302.4c-4.2 3.2-4.7 8.7-1.2 12.2L211 510.7s7.4 6.8 17.3-.8l198-163.9c4-3.2 4.4-8.7.7-12.2zm54.5-83.4L226.7 2.5c-1.5-1.2-8-5.5-16.3 1.1L3.6 165.7c-4.2 3.2-4.8 8.7-1.2 12.2l42.3 41.7 171.7 165.1c3.7 3.5 10.1 3.7 14.3.4l50.2-38.8-.3-.3 7.7-6c4.2-3.2 4.6-8.7.9-12.2l-57.1-54.4c-3.6-3.5-10-3.7-14.2-.5l-.1.1c-4.2 3.2-10.5 3.1-14.2-.4L109 180.8c-3.6-3.5-3.1-8.9 1.1-12.2l92.2-71.5c4.1-3.2 10.3-3 13.9.5l160.4 159c3.7 3.5 10 3.7 14.1.5l45.8-35.8c4.1-3.2 4.4-8.7.7-12.2z"/></svg></span><span>作品合集</span><!--[--><!--]--></a></div><!--]--><div class="navbar-item"><a style="cursor:pointer;"><span class="nav-icon"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="0 0 24 24" fill="currentColor"><path fill="none" d="M0 0h24v24H0z"/><path d="M11 2c4.968 0 9 4.032 9 9s-4.032 9-9 9-9-4.032-9-9 4.032-9 9-9zm0 16c3.867 0 7-3.133 7-7 0-3.868-3.133-7-7-7-3.868 0-7 3.132-7 7 0 3.867 3.132 7 7 7zm8.485.071l2.829 2.828-1.415 1.415-2.828-2.829 1.414-1.414z"/></svg></span><span>搜索</span></a></div></nav><!--[--><!--]--><ul class="sidebar-items"><!--[--><li><p tabindex="0" class="sidebar-item sidebar-heading">模型和机制 <!----></p><ul style="" class="sidebar-item-children"><!--[--><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#状态与流程" class="router-link-active router-link-exact-active sidebar-item" aria-label="状态与流程"><!--[--><!--]--><!----><span>状态与流程</span><!--[--><!--]--></a><ul style="" class="sidebar-item-children"><!--[--><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#功能流" class="router-link-active router-link-exact-active sidebar-item" aria-label="功能流"><!--[--><!--]--><!----><span>功能流</span><!--[--><!--]--></a><!----></li><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#保持同步" class="router-link-active router-link-exact-active sidebar-item" aria-label="保持同步"><!--[--><!--]--><!----><span>保持同步</span><!--[--><!--]--></a><!----></li><!--]--></ul></li><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#dep-ensure-标志与行为变异" class="router-link-active router-link-exact-active sidebar-item" aria-label="dep ensure 标志与行为变异"><!--[--><!--]--><!----><span>dep ensure 标志与行为变异</span><!--[--><!--]--></a><ul style="" class="sidebar-item-children"><!--[--><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#no-vendor-和-vendor-only" class="router-link-active router-link-exact-active sidebar-item" aria-label="-no-vendor 和 -vendor-only"><!--[--><!--]--><!----><span>-no-vendor 和 -vendor-only</span><!--[--><!--]--></a><!----></li><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#add" class="router-link-active router-link-exact-active sidebar-item" aria-label="-add"><!--[--><!--]--><!----><span>-add</span><!--[--><!--]--></a><!----></li><li><a aria-current="page" href="/posts/2023/4/docs/Dep/docs/references/ensure_mechanics.html#update" class="router-link-active router-link-exact-active sidebar-item" aria-label="-update"><!--[--><!--]--><!----><span>-update</span><!--[--><!--]--></a><!----></li><!--]--></ul></li><!--]--></ul></li><!--]--></ul><!--[--><!--]--></aside><!--]--><div class="page-content"><!--[--><main class="page"><!--[--><div class="article-header" style=""><!----><div class="article-header-content"><!----><h1 class="article-title"></h1><!----><div class="article-icons"><div class="article-icon"><svg class="ov-icon" style="font-size:1.08em;" aria-hidden="true" width="17.28" height="17.28" viewbox="-75.52 -43.52 599.04 599.04" fill="currentColor"><path d="M313.6 304c-28.7 0-42.5 16-89.6 16-47.1 0-60.8-16-89.6-16C60.2 304 0 364.2 0 438.4V464c0 26.5 21.5 48 48 48h352c26.5 0 48-21.5 48-48v-25.6c0-74.2-60.2-134.4-134.4-134.4zM400 464H48v-25.6c0-47.6 38.8-86.4 86.4-86.4 14.6 0 38.3 16 89.6 16 51.7 0 74.9-16 89.6-16 47.6 0 86.4 38.8 86.4 86.4V464zM224 288c79.5 0 144-64.5 144-144S303.5 0 224 0 80 64.5 80 144s64.5 144 144 144zm0-240c52.9 0 96 43.1 96 96s-43.1 96-96 96-96-43.1-96-96 43.1-96 96-96z"/></svg><span>科科人神</span></div><!----><div class="article-icon"><svg class="ov-icon" style="font-size:1.08em;" aria-hidden="true" width="17.28" height="17.28" viewbox="0 0 24 24" fill="currentColor"><path fill="none" d="M0 0h24v24H0z"/><path d="M17.618 5.968l1.453-1.453 1.414 1.414-1.453 1.453a9 9 0 11-1.414-1.414zM12 20a7 7 0 100-14 7 7 0 000 14zM11 8h2v6h-2V8zM8 1h8v2H8V1z"/></svg><span>16 min</span></div></div></div><!----></div><!--[--><!--]--><!--]--><div class="theme-gungnir-content"><!--[--><!--]--><!--[--><h1 id="模型和机制" tabindex="-1"><a class="header-anchor" href="#模型和机制" aria-hidden="true">#</a> 模型和机制</h1><p>Dep 具有许多分立组件和运动部件，所有这些部件围绕中心模型旋转。这个文档解释了模型，然后探讨了 Dep 在该模型的背景下的主要机制。</p><h2 id="状态与流程" tabindex="-1"><a class="header-anchor" href="#状态与流程" aria-hidden="true">#</a> 状态与流程</h2><p>Dep 的核心思想是&quot;四状态系统&quot;——用于对包管理器与之交互的磁盘盘上状态进行分类和组织的模型。这首先是作为一个连贯的、通用的模型来表达的。 <a href="https://medium.com/@sdboyer/so-you-want-to-write-a-package-manager-4ae9c17d9527" target="_blank" rel="noopener noreferrer">这篇(长)文章</a>，虽然四种状态模型 中的许多原理是从现有的包管理器中派生出来的。</p><p>简言之，这四种状态是:</p><ol><li>这个 <a href="/posts/2023/4/docs/Dep/docs/references/glossary.html#current-project" class="">当前项目</a> 源代码。</li><li><a href="/posts/2023/4/docs/Dep/docs/references/glossary.html#manifest" class="">manifest</a> -描述当前项目的依赖性要求的文件。在 Dep 中，这是 <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.toml.html" class=""><code>Gopkg.toml</code></a> 文件.</li><li><a href="/posts/2023/4/docs/Dep/docs/references/glossary.html#lock" class="">lock</a> -一个包含传递完整的、可再现的依赖图描述的文件.在 Dep 中，这是 <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html" class=""><code>Gopkg.lock</code></a> 文件。</li><li>源代码本身的依赖性。在 Dep 的当前设计中，这是 <code>vendor/</code> 目录。</li></ol><p>我们可以直观地表示这四个状态如下:</p><p><img src="/assets/four-states.ec08ffe0.png" alt="dep&#39;s four states"></p><h3 id="功能流" tabindex="-1"><a class="header-anchor" href="#功能流" aria-hidden="true">#</a> 功能流</h3><p>认为 Dep 是一种系统，它在这些状态之间的关系上施加单向的、功能性的流动.这些函数将上述状态作为输入和输出，将它们从左向右移动.具体来说，有两个功能:</p><ul><li>一<em>求解函数</em>将当前项目中的导入集和规则作为输入 <code>Gopkg.toml</code> 并作为其输出返回一个传递完整的、不可变的依赖图—— A 中的信息 <code>Gopkg.lock</code>.</li><li>一<em>拍卖功能</em>在 A 中获取信息 <code>Gopkg.lock</code> 作为其输入，并确保源文件的磁盘安排，使编译器将使用锁定中指定的版本。</li></ul><p>我们可以直观地表示这两个函数:</p><p><img src="/assets/annotated-func-arrows.b2ae3acd.png" alt="dep&#39;s two main functions"></p><p>这是 <code>dep ensure</code> -典型的流程，用于 <code>Gopkg.toml</code> 已经存在。当一个项目还没有 <code>Gopkg.toml</code>，<code>dep init</code> 可以生成一个。 必要的流程保持不变，但改变了输入:而不是从现有的阅读。<code>Gopkg.toml</code> 文件，<code>dep init</code> 构造从用户的 GopAs 推断出的数据中的一个， 和/或来自另一个工具的元数据文件。 换言之，<code>dep init</code> 自动将项目从其他方法迁移到组织依赖关系。</p><p>此图也直接对应于代码。解决函数实际上被分解成一个构造函数和一个方法——我们首先创 建一个 <a href="https://godoc.org/github.com/golang/dep/gps#Solver" target="_blank" rel="noopener noreferrer"><code>Solver</code></a> 类型，然后调用它的 <code>Solve()</code> 方法。 构造函数的输入被封装在一个 <a href="https://godoc.org/github.com/golang/dep/gps#SolveParameters" target="_blank" rel="noopener noreferrer"><code>SolveParameters</code></a> 看起来应该很熟悉:</p><div class="language-go ext-go line-numbers-mode"><pre class="language-go"><code><span class="token keyword">type</span> SolveParameters <span class="token keyword">struct</span> <span class="token punctuation">{</span>
	RootPackageTree pkgtree<span class="token punctuation">.</span>PackageTree <span class="token comment">// Parsed project src; contains lists of imports</span>
	Manifest gps<span class="token punctuation">.</span>RootManifest <span class="token comment">// Gopkg.toml</span>
	<span class="token operator">...</span>
<span class="token punctuation">}</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>授权功能是 <a href="https://godoc.org/github.com/golang/dep/gps#WriteDepTree" target="_blank" rel="noopener noreferrer"><code>gps.WriteDepTree()</code></a>。虽然需要少量的参数， 但相关的参数是 <a href="https://godoc.org/github.com/golang/dep/gps#Lock" target="_blank" rel="noopener noreferrer"><code>gps.Lock</code></a> -表示在 A 中保存的数据的抽象形式的接口。<code>Gopkg.lock</code>。</p><p>四态系统和这些功能流是所有DEP行为建立的基础。如果你想了解 Dep 的机制，把这个模型放在你的思维的最前沿。</p><h3 id="保持同步" tabindex="-1"><a class="header-anchor" href="#保持同步" aria-hidden="true">#</a> 保持同步</h3><p>dep 的设计目标之一是它的两个&quot;功能&quot;最小化了它们所做的工作，以及它们在各自的输出中引起的变化。因此，这两个函数在预先存在的输出处窥视，以了解实际需要做什么工作:</p><ul><li>解决函数检查现有的 <code>Gopkg.lock</code> 以确定其所有输入是否满足。如果是，则可以完全绕过求解函数。如果不是，则解决函数继续进行，但尝试更改为很少的选择。<code>Gopkg.lock</code> 尽可能。</li><li>Debug 函数已经对每个离散项目进行了哈希处理。<code>vendor/</code> 看看磁盘上的代码是什么 <code>Gopkg.lock</code> 指示应该是.只有哈希错配的项目才被重写.</li></ul><p>具体地说，Dep 定义了一些必须满足的不变量:</p><table><thead><tr><th>Sync invariant</th><th>Resolution when desynced</th><th>Func</th></tr></thead><tbody><tr><td>All <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.toml.html#required" class=""><code>required</code></a> statements in <code>Gopkg.toml</code> must be present in the <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html#input-imports" class=""><code>input-imports</code></a> list in <code>Gopkg.lock</code>.</td><td>Re-solve， update <code>Gopkg.lock</code> and <code>vendor/</code> for projects that changed</td><td>Solving</td></tr><tr><td>All <code>import</code> statements in the current project&#39;s non-<a href="/posts/2023/4/docs/Dep/docs/references/(Gopkg.toml.html#ignored)" class=""><code>ignored</code></a>， non-hidden packages must be present in <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html#input-imports" class=""><code>input-imports</code></a> list in <code>Gopkg.lock</code>.</td><td>Re-solve， update <code>Gopkg.lock</code> and <code>vendor/</code> for projects that changed</td><td>Solving</td></tr><tr><td>All <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html#version-information-revision-version-and-branch" class="">versions in <code>Gopkg.lock</code></a> must be acceptable with respect to the <code>[[constraint]]</code> or <code>[[override]]</code> declarations made in <code>Gopkg.toml</code>.</td><td>Re-solve， update <code>Gopkg.lock</code> and <code>vendor/</code> for projects that changed</td><td>Solving</td></tr><tr><td>The <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html#pruneopts" class=""><code>pruneopts</code></a> of each <code>[[project]]</code> in <code>Gopkg.lock</code> must equal the declaration in <code>Gopkg.toml</code>.</td><td>Update <code>Gopkg.lock</code> and <code>vendor/</code></td><td>Vendoring*</td></tr><tr><td>The <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.lock.html#digest" class=""><code>digest</code></a> of each <code>[[project]]</code> in <code>Gopkg.lock</code> must equal the value derived from hashing the current contents of <code>vendor/</code></td><td>Regenerate the projects in <code>vendor/</code>， and update <code>Gopkg.lock</code> with the new hash digest if necessary</td><td>Vendoring</td></tr></tbody></table><p>(*<code>pruneopts</code> 有点奇怪，因为两者之间 <code>Gopkg.toml</code> 和 <code>Gopkg.lock</code>，但这并不能解决问题)。</p><p>如果向前查看显示同步不变量已经满足，那么相应的函数不需要做任何工作;如果不满足，则 dep 采取解析步骤。无论哪种方式， 什么时候 <code>dep ensure</code> 完成后，我们可以确信，我们处于&quot;已知良好状态&quot;，所有的不变量保持不变。</p><p><code>dep check</code> 将计算所有上述关系，如果任何不变量不成立，它将打印对去同步和出口 1 的描述。此行为可以在每个项目基础上禁用， 使用 <a href="/posts/2023/4/docs/Dep/docs/references/Gopkg.toml.html#noverify" class=""><code>noverify</code> Gopkg.toml 字段</a>。</p><h2 id="dep-ensure-标志与行为变异" tabindex="-1"><a class="header-anchor" href="#dep-ensure-标志与行为变异" aria-hidden="true">#</a> <code>dep ensure</code> 标志与行为变异</h2><p>每一个 <code>dep ensure</code> 各种标志会影响解决和发布功能的行为，甚至影响它们是否运行。一些标志也会暂时导致项目不同步。在 DEP 的基本模型的背景下思考这些效应是 理解正在发生的事情的最快路径。</p><h3 id="no-vendor-和-vendor-only" tabindex="-1"><a class="header-anchor" href="#no-vendor-和-vendor-only" aria-hidden="true">#</a> <code>-no-vendor</code> 和 <code>-vendor-only</code></h3><p>这两个标志是互斥的，并决定哪一个 <code>dep ensure</code> 这两个函数实际上是被执行的。经过 <code>-no-vendor</code> 只会导致解决函数的运行，导致创建一个新的 <code>Gopkg.lock</code>; <code>-vendor-only</code>将跳过只解决版本管理功能，导致 <code>vendor/</code> 被重新填充 <code>Gopkg.lock</code>。</p><p><img src="/assets/func-toggles.5fee35f5.png" alt="Flags to run only one or the other of dep&#39;s functions"></p><p>经过 <code>-no-vendor</code> 有助于使解决功能无条件地运行，绕过通常进行的预检查。<code>Gopkg.lock</code> 看看它是否已经满足所有输入.</p><h3 id="add" tabindex="-1"><a class="header-anchor" href="#add" aria-hidden="true">#</a> <code>-add</code></h3><p>通用的目的 <code>dep ensure -add</code> 是为了便于将新的依赖项引入到 DEPGRAM 中.反之 <code>-update</code> 限于 <a href="/posts/2023/4/docs/Dep/docs/references/glossary.html#source-root" class="">源根</a>， (例如 <code>github.com/foo/bar</code>) <code>-add</code> 可以以任何包导入路径作为参数 (例如 <code>github.com/foo/bar</code> 或 <code>github.com/foo/bar/baz</code>)</p><p>从概念上讲，有两种可能的东西 <code>-add</code> 可能是介绍。任何 <code>dep ensure -add</code> 运行将至少其中之一:</p><ol><li>运行解决函数以生成新的 <code>Gopkg.lock</code> 用新的依赖(IES)</li><li>将版本约束附加到 <code>Gopkg.toml</code></li></ol><p>这意味着两个前提条件. <code>dep ensure -add</code> 其中至少有一个必须满足:</p><ol><li>命名导入路径当前不在项目的导入语句中，或者在<code>Gopkg.toml</code>的<code>required</code>列表</li><li>有 <code>[[constraint]]</code> 中 <code>Gopkg.toml</code> 对于与命名导入路径相对应的项目根</li></ol><p>还可以显式指定版本约束:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code>$ dep ensure -add github.com/foo/bar@v1.0.0
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>当参数中不包含版本约束时，求解函数将选择工作的最新版本(通常，最新的 semver 版本，如果没有 semver 版本，则选择默认的分支)。 如果求解成功，那么参数指定的版本，或者如果没有，那么由求解器选择的版本将被附加到 <code>Gopkg.toml</code>。</p><p>由输入和当前项目状态的各种差异引起的行为变化最好用矩阵表示:</p><table><thead><tr><th>Argument to <code>dep ensure -add</code></th><th>Has <code>[[constraint]]</code> stanza in <code>Gopkg.toml</code></th><th>In imports or <code>required</code></th><th>Result</th></tr></thead><tbody><tr><td><code>github.com/foo/bar</code></td><td>N</td><td>N</td><td>Added temporarily to <code>Gopkg.lock</code> &amp; <code>vendor/</code>; inferred version constraint appended to <code>Gopkg.toml</code></td></tr><tr><td><code>github.com/foo/bar@v1.0.0</code></td><td>N</td><td>N</td><td>Added temporarily to <code>Gopkg.lock</code> &amp; <code>vendor/</code>; specified version constraint appended to <code>Gopkg.toml</code></td></tr><tr><td><code>github.com/foo/bar</code></td><td>Y</td><td>N</td><td>Added temporarily to <code>Gopkg.lock</code> &amp; <code>vendor/</code></td></tr><tr><td><code>github.com/foo/bar@v1.0.0</code></td><td>Y</td><td>-</td><td><strong>Immediate error</strong>: constraint already present in <code>Gopkg.toml</code></td></tr><tr><td><code>github.com/foo/bar</code></td><td>N</td><td>Y</td><td>Infer version constraint from <code>Gopkg.lock</code> and add to <code>Gopkg.toml</code></td></tr><tr><td><code>github.com/foo/bar</code></td><td>Y</td><td>Y</td><td><strong>Immediate error:</strong> nothing to do</td></tr></tbody></table><p>对于任何路径 <code>dep ensure -add</code> 需要运行解决函数以便生成更新 <code>Gopkg.lock</code> 将来自 CLI 参数的相关信息应用于内存的表示。<code>Gopkg.toml</code>:</p><p><img src="/assets/required-arrows.1698b972.png" alt="Model modifications made by -add"></p><p>需要添加的导入路径参数通过 <code>required</code> 列表，如果指定了明确版本要求，则等于 <code>[[constraint]]</code> 创建。</p><p>虽然这些规则最终会被坚持，如果解决成功，它们至少是短暂的，直到解决成功。从求解者的角度来看，短暂的规则与源于磁盘的规则是难以区分的。因此， 对求解器，<code>dep ensure -add foo@v1.0.0</code> 与修改相同 <code>Gopkg.toml</code> 通过添加 <code>&quot;foo&quot;</code> 到 <code>required</code> 列表， 加上 <code>[[constraint]]</code> 节与 <code>version = &quot;v1.0.0&quot;</code> 然后运行 <code>dep ensure</code>。</p><p>然而，因为这些修改是短暂的，是成功的。<code>dep ensure -add</code> 可能实际上推动项目不同步。约束修改通常没有， 但是如果 <code>required</code> 列表被修改，然后该项目将不同步。用户被警告:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code>$ dep ensure -add github.com/foo/bar
<span class="token string">&quot;github.com/foo/bar&quot;</span> is not imported by your project， and has been temporarily added to Gopkg.lock and vendor/.
If you run <span class="token string">&quot;dep ensure&quot;</span> again before actually importing it， it will disappear from Gopkg.lock and vendor/.
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h3 id="update" tabindex="-1"><a class="header-anchor" href="#update" aria-hidden="true">#</a> <code>-update</code></h3><p>行为 <code>dep ensure -update</code> 与解决者自身的行为密切相关。关于这一点的完整细节是 <a href="/posts/2023/4/docs/Dep/docs/references/the-solver.html" class="">求解参考材料</a>，但为了理解的目的 <code>-update</code> 我们可以简化一点。</p><p>第一，巩固讨论中的含义。<a href="#staying-in-sync">功能优化</a> 求解函数实际上考虑了预先存在的问题。<code>Gopkg.lock</code> 运行时:</p><p><img src="/assets/lock-back.a85ffa09.png" alt="Pre-existing lock feeds back into solving function"></p><p>注射 <code>Gopkg.lock</code> 进入解决者是必要的。如果我们希望解决方案默认保存先前选定的版本，那么求解器必须了解现有的。<code>Gopkg.lock</code> 从某处。否则，它就不知道该保存什么了!</p><p>这样，锁是另一个编码到属性的属性。先前讨论 <code>SolveParameters</code> 结构。这加上另外两个属性，是最显著的。<code>-update</code>:</p><div class="language-go ext-go line-numbers-mode"><pre class="language-go"><code><span class="token keyword">type</span> SolveParameters <span class="token keyword">struct</span> <span class="token punctuation">{</span>
	<span class="token operator">...</span>
	Lock gps<span class="token punctuation">.</span>Lock <span class="token comment">// Gopkg.lock</span>
	ToChange <span class="token punctuation">[</span><span class="token punctuation">]</span>gps<span class="token punctuation">.</span>ProjectRoot <span class="token comment">// args to -update</span>
	ChangeAll <span class="token builtin">bool</span> <span class="token comment">// true if no -update args passed</span>
	<span class="token operator">...</span>
<span class="token punctuation">}</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>通常，当求解器遇到一个项目名称时，它有一个条目 <code>Gopkg.lock</code> 它把这个版本拉出来，放到这个项目的可能版本队列的头上。当特定的依赖性传 递给 <code>dep ensure -update</code> 然而，它被添加到 <code>ToChange</code> 当解决方案遇到一个列出的项目时 <code>ToChange</code> 它只是跳过锁中的版本。</p><p>&quot;跳过从锁中拉出版本&quot;意味着 <code>dep ensure -update github.com/foo/bar</code> 等同于移除 <code>[[project]]</code>节 <code>github.com/foo/bar</code> 从你 <code>Gopkg.lock</code> 然后运行 <code>dep ensure</code>。 然而，确实不推荐使用这种方法，而且将来可能会引入一些细微的改变，使等效性复杂化。</p><p>如果 <code>-update</code> 没有参数传递，则 <code>ChangeAll</code> 设置为 <code>true</code> 导致解算器忽略 <code>Gopkg.lock</code> 对于所有新遇到的项目名称。这相当于将所有依赖项显式传递为参 数。<code>dep ensure -update</code> 以及 <code>rm Gopkg.lock &amp;&amp; dep ensure</code>。 然而，这两种方法都不被推荐，未来的变化可能带来微妙的差异。</p><p>当版本提示从 <code>Gopkg.lock</code> 不是放在版本队列的最前面，这意味着 dep 将探索特定依赖项的可能版本集。这种探索是按照A来进行的。 <a href="https://godoc.org/github.com/golang/dep/gps#SortForUpgrade" target="_blank" rel="noopener noreferrer">固定排序顺序</a>，首先尝试更新版本，导致更新。</p><p>比如说有一个项目，<code>github.com/foo/bar</code>，以下版本:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code>v1.2.0， v1.1.1， v1.1.0， v1.0.0， master
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>如果我们依赖那个项目 <code>^1.1.0</code> 并拥有 <code>v1.1.0</code> 在我们 <code>Gopkg.lock</code> 这意味着有三个版本与我们的约束相匹配，其中两个版本比当前选择的版本要更 新。(还有一个较旧的版本，<code>v1.0.0</code> 和 <code>master</code> 分支，但这些是不允许的 <code>^1.1.0</code> 约束)一个普通的 <code>dep ensure</code> 运行将复制和推 <code>v1.1.0</code> 排在队伍前面的其他人:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code><span class="token punctuation">[</span>v1.1.0， v1.2.0， v1.1.1， v1.1.0， v1.0.0， master<span class="token punctuation">]</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>和 <code>v1.1.0</code> 将再次被选中，除非出现一些其他条件迫使解算器丢弃它。跑步时 <code>dep ensure -update github.com/foo/bar</code> 然而，锁定的版本没有准备好:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code><span class="token punctuation">[</span>v1.2.0， v1.1.1， v1.1.0， v1.0.0， master<span class="token punctuation">]</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>所以，除了一些其他的冲突，<code>v1.2.0</code> 被选择，导致期望的更新。</p><h4 id="update-约束类型" tabindex="-1"><a class="header-anchor" href="#update-约束类型" aria-hidden="true">#</a> <code>-update</code> 约束类型</h4><p>继续我们的例子，重要的是要注意更新 <code>-update</code> 顺便说一下，解决者从来没有明确地针对更新的版本。它只是跳过从锁中添加一个提示，然后在队列中选择 满足约束的第一个版本。因此，<code>-update</code> 只对某些类型的约束有效。</p><p>它确实适用于分支约束，我们可以通过包括基础修订来观察。如果用户已受到限制 <code>branch = &quot;master&quot;</code> 和 <code>Gopkg.lock</code> 点在一个拓扑旧版 本(例如，<code>aabbccd</code>)比规范源的顶端 <code>master</code> 分支(如: <code>bbccdde</code> ) <code>dep ensure</code> 最终将构建一个看起来像这样的队列:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code><span class="token punctuation">[</span>master@aabbccd， v1.1.0， v1.2.0， v1.1.1， v1.1.0， v1.0.0， master@bbccdde<span class="token punctuation">]</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>用 <code>-update</code> 头部的暗示将被省略; <code>branch = &quot;master&quot;</code> 将导致求解器拒绝所有语义版本，并最终解决。<code>master@bbccdde</code>。</p><p>版本队列中的所有版本都跟踪底层修订，这意味着如果，例如，一些上游项目强制推送 git 标记，那么情况也是如此:</p><div class="language-bash ext-sh line-numbers-mode"><pre class="language-bash"><code><span class="token punctuation">[</span>v1.1.0@aabbccd， v1.1.0， v1.2.0， v1.1.1， v1.1.0@bbccdde， v1.0.0， master<span class="token punctuation">]</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>因此，即使上游标记在项目的一个依赖项中被强制推送，dep 将保留原始修订，直到你显式地允许它通过 <code>dep ensure -update</code>。</p><p>这里的关键是 <code>-update</code> 的行为受指定的约束类型的约束:</p><table><thead><tr><th><code>Gopkg.toml</code> version constraint type</th><th>Constraint example</th><th><code>dep ensure -update</code> behavior</th></tr></thead><tbody><tr><td><code>version</code> (semver range)</td><td><code>&quot;^1.0.0&quot;</code></td><td>Tries to get the latest version allowed by the range</td></tr><tr><td><code>branch</code></td><td><code>&quot;master&quot;</code></td><td>Tries to move to the current tip of the named branch</td></tr><tr><td><code>version</code> (non-range semver)</td><td><code>&quot;=1.0.0&quot;</code></td><td>Change can only occur if the upstream release was moved (e.g. <code>git push --force &lt;tag&gt;</code>)</td></tr><tr><td><code>version</code> (non-semver)</td><td><code>&quot;foo&quot;</code></td><td>Change can only occur if the upstream release was moved</td></tr><tr><td><code>revision</code></td><td><code>aabbccd...</code></td><td>No change is possible</td></tr><tr><td>(none)</td><td>(none)</td><td>The first version that works， according to <a href="https://godoc.org/github.com/golang/dep/gps#SortForUpgrade" target="_blank" rel="noopener noreferrer">the sort order</a></td></tr></tbody></table><!--]--><!--[--><!--]--></div><footer class="page-meta"><!----><div class="meta-item last-updated"><span class="meta-item-label">Last Updated: </span><!----></div><!----></footer><!----><!--[--><!--]--><!----></main><!--]--></div><div class="search-page" role="search"><span class="search-close"><svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 448 512" width="28" height="28" fill="currentColor"><path d="M224 416c-8.188 0-16.38-3.125-22.62-9.375l-192-192c-12.5-12.5-12.5-32.75 0-45.25s32.75-12.5 45.25 0L224 338.8l169.4-169.4c12.5-12.5 32.75-12.5 45.25 0s12.5 32.75 0 45.25l-192 192C240.4 412.9 232.2 416 224 416z"></path></svg></span><div class="gungnir-search-box"><input placeholder="$ grep ..." autocomplete="off" spellcheck="false" value><!----></div></div><div class="menu-btn-container"><div class="menu-btn-wrapper"><div class="menu-btn"><div style="" class="menu-btn-icon"><span></span><span></span><span></span></div><div style="display:none;" class="menu-text">0</div><svg class="menu-progress"><circle class="menu-border" cx="50%" cy="50%" r="48%" style="stroke-dasharray:0% 314.15926%;"></circle></svg></div><div class="menu-btn-child-wrapper"><div class="toggle-dark-button menu-btn-child" title="toggle dark mode"><svg class="ov-icon" style="font-size:1.2em;display:none;" aria-hidden="true" width="19.2" height="19.2" viewbox="-43.52 -43.52 599.04 599.04" fill="currentColor"><path d="M256 160c-52.9 0-96 43.1-96 96s43.1 96 96 96 96-43.1 96-96-43.1-96-96-96zm246.4 80.5l-94.7-47.3 33.5-100.4c4.5-13.6-8.4-26.5-21.9-21.9l-100.4 33.5-47.4-94.8c-6.4-12.8-24.6-12.8-31 0l-47.3 94.7L92.7 70.8c-13.6-4.5-26.5 8.4-21.9 21.9l33.5 100.4-94.7 47.4c-12.8 6.4-12.8 24.6 0 31l94.7 47.3-33.5 100.5c-4.5 13.6 8.4 26.5 21.9 21.9l100.4-33.5 47.3 94.7c6.4 12.8 24.6 12.8 31 0l47.3-94.7 100.4 33.5c13.6 4.5 26.5-8.4 21.9-21.9l-33.5-100.4 94.7-47.3c13-6.5 13-24.7.2-31.1zm-155.9 106c-49.9 49.9-131.1 49.9-181 0-49.9-49.9-49.9-131.1 0-181 49.9-49.9 131.1-49.9 181 0 49.9 49.9 49.9 131.1 0 181z"/></svg><svg class="ov-icon" style="font-size:1.2em;display:none;" aria-hidden="true" width="19.2" height="19.2" viewbox="-43.52 -43.52 599.04 599.04" fill="currentColor"><path d="M283.211 512c78.962 0 151.079-35.925 198.857-94.792 7.068-8.708-.639-21.43-11.562-19.35-124.203 23.654-238.262-71.576-238.262-196.954 0-72.222 38.662-138.635 101.498-174.394 9.686-5.512 7.25-20.197-3.756-22.23A258.156 258.156 0 00283.211 0c-141.309 0-256 114.511-256 256 0 141.309 114.511 256 256 256z"/></svg><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-43.52 -43.52 599.04 599.04" fill="currentColor"><path d="M224 96l16-32 32-16-32-16-16-32-16 32-32 16 32 16 16 32zM80 160l26.66-53.33L160 80l-53.34-26.67L80 0 53.34 53.33 0 80l53.34 26.67L80 160zm352 128l-26.66 53.33L352 368l53.34 26.67L432 448l26.66-53.33L512 368l-53.34-26.67L432 288zm70.62-193.77L417.77 9.38C411.53 3.12 403.34 0 395.15 0c-8.19 0-16.38 3.12-22.63 9.38L9.38 372.52c-12.5 12.5-12.5 32.76 0 45.25l84.85 84.85c6.25 6.25 14.44 9.37 22.62 9.37 8.19 0 16.38-3.12 22.63-9.37l363.14-363.15c12.5-12.48 12.5-32.75 0-45.24zM359.45 203.46l-50.91-50.91 86.6-86.6 50.91 50.91-86.6 86.6z"/></svg></div><div class="menu-btn-child"><svg class="ov-icon" style="font-size:1.7999999999999998em;" aria-hidden="true" width="28.799999999999997" height="28.799999999999997" viewbox="-75.52 -43.52 599.04 599.04" fill="currentColor"><path d="M207.029 381.476L12.686 187.132c-9.373-9.373-9.373-24.569 0-33.941l22.667-22.667c9.357-9.357 24.522-9.375 33.901-.04L224 284.505l154.745-154.021c9.379-9.335 24.544-9.317 33.901.04l22.667 22.667c9.373 9.373 9.373 24.569 0 33.941L240.971 381.476c-9.373 9.372-24.569 9.372-33.942 0z"/></svg></div><div class="menu-btn-child"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-75.52 -43.52 599.04 599.04" fill="currentColor"><path d="M240.971 130.524l194.343 194.343c9.373 9.373 9.373 24.569 0 33.941l-22.667 22.667c-9.357 9.357-24.522 9.375-33.901.04L224 227.495 69.255 381.516c-9.379 9.335-24.544 9.317-33.901-.04l-22.667-22.667c-9.373-9.373-9.373-24.569 0-33.941L207.03 130.525c9.372-9.373 24.568-9.373 33.941-.001z"/></svg></div><!----><div class="toggle-sidebar-button menu-btn-child menu-btn-sidebar" title="toggle sidebar" aria-expanded="false" role="button" tabindex="0"><svg class="ov-icon" style="font-size:1.2em;" aria-hidden="true" width="19.2" height="19.2" viewbox="-1.6 -1.6 19.2 19.2" fill="currentColor"><path d="M14 2a1 1 0 011 1v10a1 1 0 01-1 1H2a1 1 0 01-1-1V3a1 1 0 011-1h12zM2 1a2 2 0 00-2 2v10a2 2 0 002 2h12a2 2 0 002-2V3a2 2 0 00-2-2H2z"/><path d="M3 4a1 1 0 011-1h2a1 1 0 011 1v8a1 1 0 01-1 1H4a1 1 0 01-1-1V4z"/></svg></div></div></div></div><!----></div><!--]--></div>
    <script type="module" src="/assets/app.80e5dc69.js" defer></script>
  </body>
</html>
